﻿#define _CRT_SECURE_NO_WARNINGS

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <Windows.h>
//void GetMemory(char* p)
//{
//	
//	p = (long long*)malloc(10000);
//	assert(p != NULL);
//}
//
//
//
//int main()
//{
//	char* str = NULL;//创建空指针
//	GetMemory(str);//分配内存
//	//但是因为是使用的值传递，所以调用函数后
//	//str仍然指向NULL，而不是申请的内存的首地址（内存泄露）
//	assert(str!=NULL);
//	strcpy(str, "hello world");
//	printf(str);
//	return 0;
//}
//

//正常输出"hello"是上面程序的改进
//void GetMemory(char** p, int num)
//{
//	*p = (char*)malloc(num);
//}
//void Test(void)
//{
//	char* str = NULL;
//	GetMemory(&str, 100);
//	strcpy(str, "hello");
//	printf(str);
//}
//
//int main()
//{
//	Test();
//	return 0;
//}

//char* GetMemory(void)
//{
//	char p[] = "hello world";
//	return p;
//}
//void Test(void)
//{
//	char* str = NULL;
//	str = GetMemory();
//	//此时str是一个局部变量的地址，所以printf会打印到在内存中遇到'\0'为止
//
//	printf(str);
//}
//
//
//int main()
//{
//	Test();
//	return 0;
//}

void Test(void)
{
	char* str = (char*)malloc(100);
	strcpy(str, "hello");
	free(str);//内存已释放
	if (str != NULL)//对未分配内存进行赋值
	{
		strcpy(str, "world");
		//能够输出world是因为内存释放之后没有其他修改内存的动作所以原有内存并没有被分配，维持原状
		printf(str);
		//虽然能够正常输出但是危害其实很大而且非常隐蔽（因为表面上看不出来有什么问题）。
	}
}

int main()
{
	Test();
	return 0;
}